#ifndef T_TIME_HPP
#define T_TIME_HPP

#include<string>
#include<time.h>

class TStopWatch {
private:
	static bool flagDesignatedTime;
	static bool flagSimuClockMode;
	static int64_t simuTime;
	unsigned long lastTime;
	std::string processName;
	int level;
	bool flagPrintEnable = false;
	bool flagAddedLavel = false;
	bool flagMuted = false;
	static int levelBlocked;
	static int currentSWLv;
public:
	TStopWatch();
	TStopWatch(bool flagPrintEnable);
	TStopWatch(std::string processNameNew, bool flagPrintEnable, bool flagAddLevel = true);
	~TStopWatch();
	void setFlagMuted(bool newFlag);
	void blockLowerLvs();
	static void setSimuMode();
	static void simuModeAddTimeMS(int addTimeMS);
	static void setTime(int newTime);
	void start(std::string processNameNext = "\n");
	int stop(std::string processNameNext = "\n", bool forceDisplay = false);
	void updateNameAndStop(std::string processNameOverwrite, std::string processNameNext = "\n");
	bool shoudFire(int timeout);
	int getTimeRemain(int timeout);
	static time_t getUnixTime();
	static clock_t getTimeSinceStart();
	static clock_t getRealTimeSinceStart();
	static std::string getTimeSinceStartAsString(int nDigit = -1);
	static void getDate(std::string& year, std::string& month, std::string& day);
	static std::string getDate();
};

struct TGlobalStopWatches {
	static int start(int idx, std::string processNameNext = "\n");
	static int stop(int idx, std::string processNameNext = "\n");
	static int setFlagMuted(int idx, bool newFlag);
private:
	struct TStopWatchWithoutLv {
		TStopWatch* _core;
		TStopWatchWithoutLv();
	};
	static TStopWatchWithoutLv sw[256];
};

#ifdef PLATFORM_LINUX
class stopWatchMTLinux {
private:
	timeval tStart, cTime;
	long long tPassed = 0;
	std::string processName;
	int level;
public:
	stopWatchMTLinux(int levelSet = 0);
	void start(std::string processNameNew = "\n");
	void stop(std::string processNameNew = "\n");
};
#endif

#endif